home *** CD-ROM | disk | FTP | other *** search
/ Amiga Game-Power / Amiga Game-Power.iso / anwendungen / mackie / nethack / termcap.zoo / tgoto.c < prev    next >
C/C++ Source or Header  |  1988-07-30  |  6KB  |  249 lines

  1. /************************************************************************
  2.  *                                    *
  3.  *            Copyright (c) 1982, Fred Fish                   *
  4.  *                All Rights Reserved             *
  5.  *                                    *
  6.  *    This software and/or documentation is released for public    *
  7.  *    distribution for personal, non-commercial use only.        *
  8.  *    Limited rights to use, modify, and redistribute are hereby    *
  9.  *    granted for non-commercial purposes, provided that all        *
  10.  *    copyright notices remain intact and all changes are clearly    *
  11.  *    documented.  The author makes no warranty of any kind with    *
  12.  *    respect to this product and explicitly disclaims any implied    *
  13.  *    warranties of merchantability or fitness for any particular    *
  14.  *    purpose.                            *
  15.  *                                    *
  16.  ************************************************************************
  17.  */
  18.  
  19.  
  20. /*
  21.  *  LIBRARY FUNCTION
  22.  *
  23.  *    tgoto    expand cursor addressing string from cm capability
  24.  *
  25.  *  KEY WORDS
  26.  *
  27.  *    termcap
  28.  *
  29.  *  SYNOPSIS
  30.  *
  31.  *    char *tgoto(cm,destcol,destline)
  32.  *    char *cm;
  33.  *    int destcol;
  34.  *    int destline;
  35.  *
  36.  *  DESCRIPTION
  37.  *
  38.  *    Returns cursor addressing string, decoded from the cm
  39.  *    capability string, to move cursor to column destcol on
  40.  *    line destline.
  41.  *
  42.  *    The following sequences uses one input argument, either
  43.  *    line or column, and place the appropriate substitution
  44.  *    in the output string:
  45.  *
  46.  *        %d    substitute decimal value (in ASCII)
  47.  *        %2    like %d but forces field width to 2
  48.  *        %3    like %d but forces field width to 3
  49.  *        %.    like %c
  50.  *        %+x    like %c but adds ASCII value of x
  51.  *
  52.  *    The following sequences cause processing modifications
  53.  *    but do not "use up" one of the arguments.  If they
  54.  *    act on an argument they act on the next one to
  55.  *    be converted.
  56.  *
  57.  *        %>xy    if next value to be converted is
  58.  *            greater than value of ASCII char x
  59.  *            then add value of ASCII char y.
  60.  *        %r    reverse substitution of line
  61.  *            and column (line is substituted
  62.  *            first by default).
  63.  *        %i    causes input values destcol and
  64.  *            destline to be incremented.
  65.  *        %%    gives single % character in output.
  66.  *
  67.  *  BUGS
  68.  *
  69.  *    Does not implement some of the more arcane sequences for
  70.  *    radically weird terminals (specifically %n, %B, & %D).
  71.  *    If you have one of these you deserve whatever happens.
  72.  *
  73.  */
  74.  
  75. /*
  76.  *    Miscellaneous stuff
  77.  */
  78.  
  79. #include <stdio.h>
  80. #include <string.h>
  81.  
  82. #define MAXARGS 2
  83.  
  84. static char *in;        /* Internal copy of input string pointer */
  85. static char *out;        /* Pointer to output array */
  86. static int args[MAXARGS];    /* Maximum number of args to convert */
  87. static int pcount;        /* Count of args processed */
  88. static char output[64];     /* Converted string */
  89.  
  90.  
  91. /*
  92.  *  PSEUDO CODE
  93.  *
  94.  *    Begin tgoto
  95.  *        If no string to process then
  96.  *        Return pointer to error string.
  97.  *        Else
  98.  *        Initialize pointer to input string.
  99.  *        Initialize pointer to result string.
  100.  *        First arg is line number by default.
  101.  *        Second arg is col number by default.
  102.  *        No arguments processed yet.
  103.  *        While there is another character to process
  104.  *            If character is a not a % character then
  105.  *            Simply copy to output.
  106.  *            Else
  107.  *            Process the control sequence.
  108.  *            End if
  109.  *        End while
  110.  *        Return pointer to static output string.
  111.  *        End if
  112.  *    End tgoto
  113.  *
  114.  */
  115.  
  116. char *tgoto(cm,destcol,destline)
  117. char *cm;
  118. int destcol;
  119. int destline;
  120. {
  121.     if (cm == NULL) {
  122.     return("OOPS");
  123.     } else {
  124.     in = cm;
  125.     out = output;
  126.     args[0] = destline;
  127.     args[1] = destcol;
  128.     pcount = 0;
  129.     while (*in != NULL) {
  130.         if (*in != '%') {
  131.         *out++ = *in++;
  132.         } else {
  133.         process();
  134.         }
  135.     }
  136.     return(output);
  137.     }
  138. }
  139.  
  140. /*
  141.  *  INTERNAL FUNCTION
  142.  *
  143.  *    process   process the conversion/command sequence
  144.  *
  145.  *  SYNOPSIS
  146.  *
  147.  *    static process()
  148.  *
  149.  *  DESCRIPTION
  150.  *
  151.  *    Processes the sequence beginning with the % character.
  152.  *    Directly manipulates the input string pointer, the
  153.  *    output string pointer, and the arguments.  Leaves
  154.  *    the input string pointer pointing to the next character
  155.  *    to be processed, and the output string pointer pointing
  156.  *    to the next output location.  If conversion of
  157.  *    one of the numeric arguments occurs, then the pcount
  158.  *    is incremented.
  159.  *
  160.  */
  161.  
  162. /*
  163.  *  PSEUDO CODE
  164.  *
  165.  *    Begin process
  166.  *        Skip over the % character.
  167.  *        Switch on next character after %
  168.  *        Case 'd':
  169.  *        Process %d type conversion (variable width).
  170.  *        Reinitialize output pointer.
  171.  *        Break;
  172.  *        Case '2':
  173.  *        Process %d type conversion (width 2).
  174.  *        Reinitialize output pointer.
  175.  *        Break;
  176.  *        Case '3':
  177.  *        Process %d type conversion (width 3).
  178.  *        Reinitialize output pointer.
  179.  *        Break;
  180.  *        Case '.'
  181.  *        Process %c type conversion.
  182.  *        Break;
  183.  *        Case '+':
  184.  *        Process %c type conversion with offset.
  185.  *        Break;
  186.  *        Case '>':
  187.  *        Process argument modification.
  188.  *        Break;
  189.  *        Case 'r':
  190.  *        Process argument reversal.
  191.  *        Break;
  192.  *        Case 'i':
  193.  *        Increment argument values.
  194.  *        Break;
  195.  *        Case '%':
  196.  *        Copy to output, incrementing pointers.
  197.  *        Break;
  198.  *        End switch
  199.  *    End process
  200.  *
  201.  */
  202.  
  203.  
  204. static process()
  205. {
  206.     int temp;
  207.  
  208.     in++;
  209.     switch(*in++) {
  210.     case 'd':
  211.     sprintf(out,"%d",args[pcount++]);
  212.     out = &output[strlen(output)];
  213.     break;
  214.     case '2':
  215.     sprintf(out,"%02d",args[pcount++]);
  216.     out = &output[strlen(output)];
  217.     break;
  218.     case '3':
  219.     sprintf(out,"%03d",args[pcount++]);
  220.     out = &output[strlen(output)];
  221.     break;
  222.     case '.':
  223.     *out++ = args[pcount++];
  224.     break;
  225.     case '+':
  226.     *out++ = args[pcount++] + *in++;
  227.     break;
  228.     case '>':
  229.     if (args[pcount] > *in++) {
  230.         args[pcount] += *in++;
  231.     } else {
  232.         in++;
  233.     }
  234.     break;
  235.     case 'r':
  236.     temp = args[pcount];
  237.     args[pcount] = args[pcount+1];
  238.     args[pcount+1] = temp;
  239.     break;
  240.     case 'i':
  241.     args[pcount]++;
  242.     args[pcount+1]++;
  243.     break;
  244.     case '%':
  245.     *out++ = '%';
  246.     break;
  247.     }
  248. }
  249.